#include "rollingsection.h"


RollingSection::RollingSection(QWidget *parent)
    :QWidget(parent)
{
    /* 去边框,同时保留窗口原有的属性 */
    this->setWindowFlags(Qt::FramelessWindowHint | windowFlags());;
    /* 设置背景样式 */
    this->setStyleSheet("background:white;");
    /* 设置动画目标 */
    rollingAni.setTargetObject(this);
    /* 设置动画目标属性 */
    rollingAni.setPropertyName("posYShifting");
    /* 设置动画持续时间 */
    rollingAni.setDuration(500);
    /* 设置动画曲线样式 */
    rollingAni.setEasingCurve(QEasingCurve::OutCirc);
}

RollingSection::RollingSection(int min, int max, int section, QWidget *parent)
        :QWidget(parent)
{
    /* 去边框,同时保留窗口原有的属性 */
    this->setWindowFlags(Qt::FramelessWindowHint | windowFlags());;
    /* 设置背景样式 */
    this->setStyleSheet("background:white;");
    /* 设置动画目标 */
    rollingAni.setTargetObject(this);
    /* 设置动画目标属性 */
    rollingAni.setPropertyName("posYShifting");
    /* 设置动画持续时间 */
    rollingAni.setDuration(500);
    /* 设置动画曲线样式 */
    rollingAni.setEasingCurve(QEasingCurve::OutCirc);
    setRange(min,max);
    setSectionType(section);
}

RollingSection::~RollingSection()
{

}

void RollingSection::setRange(int min, int max)
{
    this->min_Range = min;
    this->max_Range = max;
    /* 如果选中的当前值小于最小值，就等于最小值 */
    if(currentValue < min){
        currentValue = min;
    }
    /* 最大值同理 */
    if(currentValue > max){
        currentValue = max;
    }
    update();
}

int RollingSection::PosYShifting()
{
    /* 注册属性取值函数 */
    return posYShifting;
}

void RollingSection::setPosYShifting(int posYShifting)
{
    /* 注册属性赋值函数 */
    this->posYShifting = posYShifting;
    update();
}

void RollingSection::mousePressEvent(QMouseEvent *event)
{
    rollingAni.stop();
    /* 开启鼠标拖动滚动判决 */
    rollingJudgment = true;
    /* 刷新按下时鼠标位置 */
    currentPosY = event->pos().y();
}

void RollingSection::wheelEvent(QWheelEvent *event)
{
    /* 以滚轮delta值正负性作为判决条件进行判决 */
    if(event->delta()>0)
    {
        if(currentValue > min_Range){
            posYShifting = this->height()/4;
        }
    }
    else{
        if(currentValue < max_Range){
            posYShifting = - this->height()/4;
        }
    }
    rollAnimation();
    update();
}

void RollingSection::mouseMoveEvent(QMouseEvent *event)
{
    if(rollingJudgment)
    {
        /*边界判决，防止超出范围*/
        if((currentValue == min_Range && event->pos().y() >= currentPosY)
                ||(currentValue == max_Range && event->pos().y() <= currentPosY)){
            return;
        }
        else{
            /*计算鼠标拖动时的垂直偏移量*/
            posYShifting = event->pos().y() - currentPosY;
        }
        update();
    }
}

void RollingSection::mouseReleaseEvent(QMouseEvent *event)
{
    Q_UNUSED(event);
    /*拖动判决归位*/
    if(rollingJudgment)
    {
        rollingJudgment = false;
        /* 开启动画 */
        rollAnimation();
    }
}

void RollingSection::paintEvent(QPaintEvent *paint)
{
    Q_UNUSED(paint);
    /* 创建画笔对象 */
    QPainter painter(this);
    /* 画笔抗锯齿操作 */
    painter.setRenderHint(QPainter::TextAntialiasing);
    painter.setRenderHint(QPainter::Antialiasing, true);

    /* 偏移量检测，以1/4高度和取值范围为边界 */
    if(posYShifting >= height() / 4 && currentValue > min_Range)
    {
        /* 鼠标起始位置归位，即加上1/4的高度 */
        currentPosY += height()/4;
        /* 偏移量归位，即减去1/4的高度 */
        posYShifting -= height()/4;
        /* currentValue自减 */
        currentValue -= 1;
    }
    if(posYShifting <= -height() / 4 && currentValue < max_Range)
    {
        currentPosY -= height() / 4;
        posYShifting += height() / 4;
        currentValue += 1;
    }

    /* 调用函数画出数字currentValue */
    drawNumber(painter,currentValue,posYShifting);

    /* 调用函数画出两侧数字 */
    if(currentValue != min_Range){
        drawNumber(painter,currentValue - 1,posYShifting - height() / 4);
    }
    if(currentValue != max_Range){
        drawNumber(painter,currentValue + 1,posYShifting + height() / 4);
    }

    /* 调用函数画出两侧数字 */
    if(posYShifting >= 0 && currentValue - 2 >= min_Range){
        drawNumber(painter,currentValue - 2,posYShifting - height() / 2);
    }

    if(posYShifting <= 0 && currentValue + 2 <= max_Range){
        drawNumber(painter,currentValue + 2,posYShifting + height() /  2);
    }

    /* 画出数字currentValue两侧边框 */
    painter.setPen(QPen(QColor(70,144,249),2));
    painter.drawLine(0,height() / 8 * 3,width(),height() / 8 * 3);
    painter.drawLine(0,height() / 8 * 5,width(),height() / 8 * 5);
}

void RollingSection::drawNumber(QPainter &painter, int value, int offset)
{
    /* 通过偏移量控制数字大小size */
    int size = (this->height() - abs(offset)) / numberSize;
    /* 通过偏移量控制数字透明度transparency */
    int transparency = 255 - 510 * abs(offset) / height();
    /* 通过偏移量控制数字在ui界面占据空间高度height */
    int height = this->height() / 2 - 3 * abs(offset) / 5;
    /* 计算数字显示位置 */
    int y = this->height() / 2 + offset - height / 2;

    QFont font;
    /* 设置字体大小 */
    font.setPixelSize(size);
    /* 画笔设置字体 */
    painter.setFont(font);
    /* 画笔设置颜色 */
    painter.setPen(QColor(0,0,0,transparency));
    /* 画笔painter画出文本*/
    painter.drawText(QRectF(0,y,width(),height),Qt::AlignCenter,(QString::number(value) + typeOfChar));
}

void RollingSection::rollAnimation()
{
    /* 动画判决，达到条件开启相应动画 */
    if(posYShifting > height() / 8)
    {
        /* 设置属性动画初始value */
        rollingAni.setStartValue(height() / 8 - posYShifting);
        /* 设置属性动画终止value */
        rollingAni.setEndValue(0);
        /* currentValue值变更 */
        setCurrentValue(currentValue - 1);
    }
    else if(posYShifting > -height() / 8)
    {
        /* 设置属性动画初始value */
        rollingAni.setStartValue(posYShifting);
        /* 设置属性动画终止value */
        rollingAni.setEndValue(0);
    }
    else if(posYShifting < -height() / 8)
    {
        /* 设置属性动画初始value */
        rollingAni.setStartValue(-height() / 8 - posYShifting);
        /* 设置属性动画终止value */
        rollingAni.setEndValue(0);
        /* currentValue值变更 */
        setCurrentValue(currentValue + 1);
    }
    /* 动画开始 */
    rollingAni.start();
    update();
}

void RollingSection::timeInitial()
{
    /* 取系统的对应时间作为滚动时间选择的初始值并将typeOfChar初始化对应值 */
    switch (sectionType) {
    case Enum::YEAR :
        currentValue = QDateTime::currentDateTime().toString("yyyy").toInt();
        typeOfChar = "年";
        break;
    case Enum::MONTH :
        currentValue = QDateTime::currentDateTime().toString("MM").toInt();
        typeOfChar = "月";
        break;
    case Enum::DAY :
        currentValue = QDateTime::currentDateTime().toString("dd").toInt();
        typeOfChar = "日";
        break;
    case Enum::HOUR:
        currentValue = QDateTime::currentDateTime().toString("hh").toInt();
        typeOfChar = "时";
        break;
    case Enum::MINUTE :
        currentValue = QDateTime::currentDateTime().toString("mm").toInt();
        typeOfChar = "分";
        break;
    case Enum::SECOND :
        currentValue = QDateTime::currentDateTime().toString("ss").toInt();
        typeOfChar = "秒";
        break;
    default:
        return;
    }
}

void RollingSection::setSectionType(int type)
{
    this->sectionType = type;
    timeInitial();
    update();
}

int RollingSection::CurrentValue()
{
    return currentValue;
}

void RollingSection::setCurrentValue(int currentValue)
{
    if (this->currentValue == currentValue)
        return;

    this->currentValue = currentValue;
    emit CurrentValueChanged(currentValue);
    update();
}
